package org.kongcloud.spring;

import org.springframework.beans.BeansException;
import org.springframework.beans.factory.config.ConfigurableListableBeanFactory;
import org.springframework.beans.factory.support.BeanDefinitionRegistry;
import org.springframework.beans.factory.support.BeanDefinitionRegistryPostProcessor;
import org.springframework.stereotype.Component;
import org.springframework.util.StringUtils;

import java.io.*;
import java.util.Arrays;
import java.util.HashSet;
import java.util.List;

@Component
public class SpringFrameworkPostProcessor implements BeanDefinitionRegistryPostProcessor {
    public static String LINE_SEP = System.lineSeparator();
    public static String TOKEN = "@";
    private void load(String fileName, HashSet<String> filterMap) {
        File file = new File(fileName);
        if (!file.exists()) {
            return;
        }
        try (BufferedReader br = new BufferedReader(new FileReader(fileName))) {
            String line;
            while ((line = br.readLine()) != null) {
                if (StringUtils.hasText(line) && !line.startsWith("#")) {
                    filterMap.add(line.trim());
                }
            }
        } catch (IOException e) {
            //e.printStackTrace();
        }
    }

    private void writeFile(String fileName, String content) {
        try {
            BufferedWriter bufferedWriter = new BufferedWriter(new FileWriter(fileName, true));
            bufferedWriter.write(content);
            bufferedWriter.newLine();
            bufferedWriter.flush();
        } catch (IOException e) {
            //throw new RuntimeException(e);
        }
    }

    @Override
    public void postProcessBeanDefinitionRegistry(BeanDefinitionRegistry registry) throws BeansException {
        String[] names = registry.getBeanDefinitionNames();
        String filter = System.getProperty("spring.application.config.bean.filter");
        String tempDir = System.getProperty("java.io.tmpdir");
        String fileName = tempDir + File.separator + "spring.bean.init";
        String fileNameLocal = "spring.bean.init";
        String logFile = tempDir + File.separator + "spring.bean.log";

        HashSet<String> filterMap = new HashSet<>();
        load(fileName, filterMap);
        load(fileNameLocal, filterMap);
        if (StringUtils.hasText(filter)) {
            List<String> splits = Arrays.asList(filter.split(","));
            if (!splits.isEmpty()) {
                filterMap.addAll(splits);
            }
        }

        for (String bean : names) {
            if (!StringUtils.hasText(bean)) continue;
            writeFile(logFile, "[bean]" + bean);
            for (String filterName : filterMap) {
                if (!StringUtils.hasText(filterName)) continue;
                if (bean.toLowerCase().endsWith(filterName.toLowerCase())) {
                    writeFile(logFile, "[remove]:" + filterName);
                    registry.removeBeanDefinition(bean);
                }
            }
        }
    }

    @Override
    public void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException {

    }
}